home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 2000 November: Tool Chest / Dev.CD Nov 00 TC Disk 1.toast / Sample Code / Graphics 3D / RAVE Starter Samples / RAVE CommonCode / RAVE Utilities.cp < prev    next >
Encoding:
Text File  |  2000-09-28  |  7.2 KB  |  260 lines  |  [TEXT/CWIE]

  1. /*
  2.     File:        RAVE Utilities.cp
  3.  
  4.     Contains:    RAVE Utilities defines a number of useful functions for working with RAVE,
  5.                 including functions to find the deepest GDevice, loading textures from a PICT
  6.                 resource, and so on. Essentially, it defines a number of pieces of common code
  7.                 that were useful to many of my projects.
  8.  
  9.     Written by: Timothy Carroll    
  10.  
  11.     Copyright:    Copyright ©1996-1999 by Apple Computer, Inc., All Rights Reserved.
  12.  
  13.                 You may incorporate this Apple sample source code into your program(s) without
  14.                 restriction. This Apple sample source code has been provided "AS IS" and the
  15.                 responsibility for its operation is yours. You are not permitted to redistribute
  16.                 this Apple sample source code as "Apple sample source code" after having made
  17.                 changes. If you're going to re-distribute the source, we require that you make
  18.                 it clear in the source that the code was descended from Apple sample source
  19.                 code, but that you've made changes.
  20.  
  21.     Change History (most recent first):
  22.                 7/15/1999    Karl Groethe    Updated for Metrowerks Codewarror Pro 2.1
  23.                 
  24.  
  25. */
  26. #include <fp.h>
  27. #include "Rave Utilities.h"
  28. #include "common stuff.h"
  29. #include <Memory.h>
  30. #include <Resources.h>
  31.  
  32.  
  33.  
  34. /*****************************************************************************
  35. LOOKUP TABLES
  36.  
  37. I use SIN and COS in a number of places, and we don't need perfect precision,
  38. so we generate a set of lookup tables on 0.5 degree increments.  Most of the
  39. 3D math routines use these lookups to generate matrices.
  40. *****************************************************************************/
  41.  
  42. float gSinArray[721]; // [720] = [0]
  43. float gCosArray[721]; // [720] = [0]
  44.  
  45. OSStatus InitializeLookups(void)
  46. {
  47.     int loop;
  48.     
  49.     for (loop = 0; loop < 720; loop++)
  50.     {
  51.         double angle = (loop * 0.5)/57.296;
  52.         
  53.         gSinArray[loop] = sin (angle);
  54.         gCosArray[loop] = cos (angle);
  55.     }
  56.     
  57.     gSinArray[720] = gSinArray[0];
  58.     gCosArray[720] = gCosArray[0];
  59.     
  60.     return noErr;
  61. }
  62.  
  63.  
  64.  
  65. /*****************************************************************************
  66. RAVE ENGINE FUNCTIONS
  67.     
  68. FindTextureMappingEngine walks the list of available engines and returns
  69. the first engine capable of Texture Mapping that will run on the device.
  70.  
  71. GetListOfEngines creates a handle filled with references to all engines
  72. available to the application that run on the GDevice passed in the routine.
  73. Pass in NULL to find all engines.
  74. *****************************************************************************/
  75.  
  76. TQAEngine    *FindTextureMappingEngine (TQADevice *device)
  77. {
  78.     TQAEngine         *engine = NULL;
  79.     TQAError        theQAErr = kQANoErr;
  80.     unsigned long    features;
  81.     
  82.     engine = QADeviceGetFirstEngine (device);
  83.     
  84.     while (engine != NULL)
  85.     {
  86.         theQAErr = QAEngineGestalt (engine,
  87.                                     kQAGestalt_OptionalFeatures, 
  88.                                     &features);
  89.                                     
  90.         if ((theQAErr == kQANoErr) && (features & kQAOptional_Texture))
  91.             return engine;
  92.             
  93.         engine = QADeviceGetNextEngine (device, engine);
  94.     }
  95.     
  96.     // Failed to find an engine that supports texture mapping
  97.     return NULL;
  98. }
  99.  
  100.  
  101. OSStatus    GetListOfEngines (GDHandle screen, Handle *list, long *number)
  102. {
  103.     OSStatus    theErr = noErr;
  104.     TQAError    theQAErr = kQANoErr;
  105.     
  106.     long        loop, tempCount;
  107.     Handle        tempList;
  108.     
  109.     // We need a device structure to build the list of engines.
  110.     // We only need to set it up if we were passed a GDevice.
  111.     TQADevice    device, *devicePtr = NULL;
  112.     TQAEngine    *engine;
  113.     
  114.     if (screen)
  115.     {
  116.         device.deviceType = kQADeviceGDevice;
  117.         device.device.gDevice = screen;
  118.         devicePtr = &device;
  119.     }
  120.     
  121. // We walk the list of engines twice.  First, we count the number
  122. // of engines, and allocate a handle large enough to hold the
  123. // engine references.  Second, we walk the list a second time and
  124. // stuff the handle.
  125.  
  126. // The software engine should always be available, so I consider
  127. // a count of 0 to be an error.
  128.  
  129.     tempCount = 0;
  130.     engine = QADeviceGetFirstEngine (devicePtr);
  131.     while (engine != NULL)
  132.     {
  133.         tempCount++;
  134.         engine = QADeviceGetNextEngine (devicePtr, engine);
  135.     }
  136.     
  137.     if (tempCount == 0)
  138.         SIGNAL_ERROR ("\pERROR: No Engines available for this GDevice")
  139.      
  140. // Allocate a handle for the list.
  141.     tempList = NewHandle (tempCount * sizeof (TQAEngine *));
  142.     theErr = MemError();
  143.     FAIL_OSERR (theErr, "\pError:Unable to allocate a handle for the engine list")
  144.     FAIL_NIL(tempList, "\pError:Unable to allocate a handle for the engine list")
  145.  
  146. // Walk the list again and stuff the references into the handle
  147.     engine = QADeviceGetFirstEngine (devicePtr);
  148.     
  149.     for (loop = 0; loop < tempCount; loop++)
  150.     {
  151.         (*(TQAEngine ***)tempList)[loop] = engine;
  152.         engine = QADeviceGetNextEngine (devicePtr, engine);
  153.     }
  154.     
  155. // Everything went successfully, fill in the list and count and return no error;
  156.     *list = tempList;
  157.     *number = tempCount;
  158.     
  159.     goto cleanup;
  160.  
  161. error:
  162. // If an error occurred, clear the list and return the error.
  163.     if (theErr == noErr)
  164.         theErr = paramErr;
  165.         
  166.     if (tempList)
  167.         DisposeHandle (tempList);    
  168.         
  169.     *list = NULL;
  170.     *number = 0;
  171.  
  172. cleanup:
  173.     
  174.     return theErr;
  175. }
  176.  
  177.  
  178. TQATexture    *LoadTextureFromPictResource (TQAEngine *engine, short pictID)
  179. {
  180.     TQAError        theQAErr = kQANoErr;
  181.     OSStatus        theErr = noErr;
  182.  
  183.     TQAImage        image;
  184.     TQATexture        *texture= NULL;
  185.     
  186.     PicHandle        picture = NULL;
  187.     Rect            pictRect;
  188.     GWorldPtr        pictWorld = NULL;
  189.     PixMapHandle    pictPix = NULL;
  190.     
  191.     CGrafPtr        savePort = NULL;
  192.     GDHandle        saveDevice = NULL;
  193.     
  194. // Load the texture from the resource;
  195.     
  196.     picture = GetPicture (pictID);
  197.     theErr = ResError();
  198.     FAIL_NIL (picture, "\pERROR: Failed to load the texture resource")
  199.     FAIL_OSERR (theErr,"\pERROR: Failed to load the texture resource")
  200.     
  201. // for now, we assume that the PICT is a valid size -- that is,
  202. // it should be a power of 2 in both dimensions.
  203.     
  204. // Create a 32-bit GWorld to hold the pix map data.
  205.     pictRect = (**picture).picFrame;
  206.     OffsetRect (&pictRect, -pictRect.left, -pictRect.top);
  207.     
  208.     theErr = NewGWorld(&pictWorld, 32, &pictRect, NULL, NULL, NULL);
  209.     FAIL_OSERR (theErr, "\pERROR:Couldn't create the texture gworld")
  210.     FAIL_NIL (pictWorld,"\pERROR:Couldn't create the texture gworld")
  211.     
  212.     pictPix = GetGWorldPixMap (pictWorld);
  213.     FAIL_NIL (pictPix, "\pERROR:Couldn't retrieve the texture PixMap")
  214.     FAIL_FALSE (LockPixels (pictPix),"\pERROR:Couldn't lock the texture PixMap")
  215.     
  216. // Draw the picture into the GWorld
  217.     GetGWorld (&savePort, &saveDevice);
  218.     SetGWorld (pictWorld, NULL);
  219.     DrawPicture(picture, &pictRect);
  220.     SetGWorld (savePort, saveDevice);
  221.  
  222. // Fill in the image structure to describe our GWorld and create the texture
  223.     image.width = pictRect.right;
  224.     image.height = pictRect.bottom;
  225.     image.rowBytes = (**pictPix).rowBytes & 0x3FFF;
  226.     image.pixmap = GetPixBaseAddr (pictPix);
  227.     
  228. // Create the texture and detach it so that the engine is responsible for it
  229.     theQAErr = QATextureNew (engine,kQATexture_None ,kQAPixel_RGB32,&image, &texture);
  230.     if (theQAErr != kQANoErr) SIGNAL_ERROR ("\pError: RAVE failed to allocate the texture")
  231.     
  232.     theQAErr = QATextureDetach (engine, texture); 
  233.     if (theQAErr != kQANoErr) SIGNAL_ERROR ("\pError: RAVE failed to detach the texture")
  234.     
  235. // We're done -- jump to the cleanup code and return.
  236.     goto cleanup;
  237.     
  238. error:
  239. // We hit an error, so we need to make sure we cleanup 
  240. // everything and return a NULL texture
  241.     if (texture != NULL)
  242.         QATextureDelete (engine, texture);
  243.     texture = NULL;
  244.     
  245. cleanup:
  246.     if (picture != NULL)
  247.         ReleaseResource ((Handle) picture);
  248.     if (pictWorld != NULL)
  249.         DisposeGWorld (pictWorld);
  250.     
  251.     return texture;
  252. }
  253.  
  254.  
  255.  
  256.  
  257.  
  258.  
  259.  
  260.